Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Introduce OptimizerRule::rewrite to rewrite in place, rewrite ExprSimplifier (20% faster planning) #9954

Merged
merged 1 commit into from
Apr 11, 2024

Conversation

alamb
Copy link
Contributor

@alamb alamb commented Apr 4, 2024

Note: A substantial number of the changes in this PR are removing & in tests. The actual logic change is quite small

Which issue does this PR close?

Part of #9637

Rationale for this change

The less copying in the planner, the less time it takes to plan a query. Profiling from thesql_planner benchmark in #9637 shows almost 25% of the time is spent in ExprSimplifier, so let's make that faster.

The current API of OptimizerRule s requires a copy of the LogicalPlan to be made. Thus we need a new API that allows for in place rewrites.

What changes are included in this PR?

  1. Add new OptimizerRule::rewrite API for in place rewrites
  2. Update Optimizer to use the new API
  3. Update ExprSimplifier to implement rewrite rather than try_optimize

Open questions:

  1. should we deprecate the old OptimizerRule API (I think so -- maybe we can do this as a follow on PR)

Are these changes tested?

Yes by existing tests

Performance benchmark: 22% faster TPC-H planning, 26% faster TPC-DS planning

Details

++ critcmp main simplify_exprs_no_copy
group                                         main                                   simplify_exprs_no_copy
-----                                         ----                                   ----------------------
logical_aggregate_with_join                   1.00  1189.1±11.74µs        ? ?/sec    1.00  1186.6±10.71µs        ? ?/sec
logical_plan_tpcds_all                        1.00    155.7±0.85ms        ? ?/sec    1.00    155.6±0.98ms        ? ?/sec
logical_plan_tpch_all                         1.00     16.7±0.18ms        ? ?/sec    1.00     16.7±0.15ms        ? ?/sec
logical_select_all_from_1000                  1.06     19.3±0.11ms        ? ?/sec    1.00     18.2±0.56ms        ? ?/sec
logical_select_one_from_700                   1.00   782.8±19.70µs        ? ?/sec    1.00    780.6±8.10µs        ? ?/sec
logical_trivial_join_high_numbered_columns    1.00   732.4±18.61µs        ? ?/sec    1.00    732.4±9.34µs        ? ?/sec
logical_trivial_join_low_numbered_columns     1.00    714.8±6.80µs        ? ?/sec    1.00    716.0±6.69µs        ? ?/sec
physical_plan_tpcds_all                       1.26   1847.2±3.05ms        ? ?/sec    1.00   1470.4±3.99ms        ? ?/sec
physical_plan_tpch_all                        1.22    119.8±0.74ms        ? ?/sec    1.00     98.2±0.66ms        ? ?/sec
physical_plan_tpch_q1                         1.37      7.3±0.07ms        ? ?/sec    1.00      5.4±0.02ms        ? ?/sec
physical_plan_tpch_q10                        1.20      5.5±0.03ms        ? ?/sec    1.00      4.6±0.03ms        ? ?/sec
physical_plan_tpch_q11                        1.20      4.8±0.03ms        ? ?/sec    1.00      4.0±0.02ms        ? ?/sec
physical_plan_tpch_q12                        1.19      3.9±0.03ms        ? ?/sec    1.00      3.3±0.02ms        ? ?/sec
physical_plan_tpch_q13                        1.18      2.6±0.01ms        ? ?/sec    1.00      2.2±0.01ms        ? ?/sec
physical_plan_tpch_q14                        1.18      3.4±0.02ms        ? ?/sec    1.00      2.9±0.01ms        ? ?/sec
physical_plan_tpch_q16                        1.23      4.9±0.03ms        ? ?/sec    1.00      4.0±0.02ms        ? ?/sec
physical_plan_tpch_q17                        1.24      4.6±0.03ms        ? ?/sec    1.00      3.8±0.02ms        ? ?/sec
physical_plan_tpch_q18                        1.22      5.0±0.03ms        ? ?/sec    1.00      4.1±0.02ms        ? ?/sec
physical_plan_tpch_q19                        1.21      9.4±0.15ms        ? ?/sec    1.00      7.8±0.15ms        ? ?/sec
physical_plan_tpch_q2                         1.24     10.5±0.07ms        ? ?/sec    1.00      8.5±0.06ms        ? ?/sec
physical_plan_tpch_q20                        1.26      6.1±0.04ms        ? ?/sec    1.00      4.8±0.03ms        ? ?/sec
physical_plan_tpch_q21                        1.24      8.3±0.05ms        ? ?/sec    1.00      6.7±0.05ms        ? ?/sec
physical_plan_tpch_q22                        1.23      4.4±0.03ms        ? ?/sec    1.00      3.6±0.02ms        ? ?/sec
physical_plan_tpch_q3                         1.18      3.9±0.03ms        ? ?/sec    1.00      3.3±0.02ms        ? ?/sec
physical_plan_tpch_q4                         1.20      2.9±0.02ms        ? ?/sec    1.00      2.4±0.03ms        ? ?/sec
physical_plan_tpch_q5                         1.16      5.6±0.04ms        ? ?/sec    1.00      4.8±0.03ms        ? ?/sec
physical_plan_tpch_q6                         1.15  1996.9±10.25µs        ? ?/sec    1.00  1739.6±86.99µs        ? ?/sec
physical_plan_tpch_q7                         1.22      7.5±0.11ms        ? ?/sec    1.00      6.2±0.07ms        ? ?/sec
physical_plan_tpch_q8                         1.20      9.6±0.05ms        ? ?/sec    1.00      8.0±0.07ms        ? ?/sec
physical_plan_tpch_q9                         1.21      7.2±0.04ms        ? ?/sec    1.00      6.0±0.03ms        ? ?/sec
physical_select_all_from_1000                 1.47    128.4±0.49ms        ? ?/sec    1.00     87.1±0.31ms        ? ?/sec
physical_select_one_from_700                  1.10      4.0±0.03ms        ? ?/sec    1.00      3.7±0.02ms        ? ?/sec

Are there any user-facing changes?

Faster planning 🚀

@github-actions github-actions bot added logical-expr Logical plan and expressions optimizer Optimizer rules core Core DataFusion crate sqllogictest SQL Logic Tests (.slt) labels Apr 4, 2024
@alamb alamb force-pushed the alamb/simplify_exprs_no_copy branch from 4f99bfc to 6be96c2 Compare April 5, 2024 10:06
@alamb alamb changed the title Introduce OptimizerRule::try_optimize_owned to rewrite in place Introduce OptimizerRule::try_optimize_owned to rewrite in place, rewrite ExprSimplifier Apr 5, 2024
@alamb alamb changed the title Introduce OptimizerRule::try_optimize_owned to rewrite in place, rewrite ExprSimplifier Introduce OptimizerRule::try_optimize_owned to rewrite in place, rewrite ExprSimplifier Apr 5, 2024
@alamb alamb force-pushed the alamb/simplify_exprs_no_copy branch 3 times, most recently from 168f63f to dacbfa6 Compare April 7, 2024 18:00
@alamb alamb changed the title Introduce OptimizerRule::try_optimize_owned to rewrite in place, rewrite ExprSimplifier Introduce OptimizerRule::rewrite to rewrite in place, rewrite ExprSimplifier Apr 10, 2024
@alamb alamb force-pushed the alamb/simplify_exprs_no_copy branch from dacbfa6 to d95eca4 Compare April 10, 2024 11:01
@github-actions github-actions bot removed the logical-expr Logical plan and expressions label Apr 10, 2024
@alamb alamb force-pushed the alamb/simplify_exprs_no_copy branch from d95eca4 to 6d31211 Compare April 10, 2024 11:20
@alamb alamb changed the title Introduce OptimizerRule::rewrite to rewrite in place, rewrite ExprSimplifier Introduce OptimizerRule::rewrite to rewrite in place, rewrite ExprSimplifier (20% faster planning) Apr 10, 2024
@alamb alamb force-pushed the alamb/simplify_exprs_no_copy branch from c9ff49b to e31a358 Compare April 10, 2024 13:35
@github-actions github-actions bot removed the sqllogictest SQL Logic Tests (.slt) label Apr 10, 2024

plan.with_new_exprs(exprs, new_inputs)
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The whole point of this PR is to remove the calls to expressions and new_with_exprs (which requires cloning all the expressions)

@@ -109,18 +127,22 @@ impl SimplifyExpressions {
simplifier
};

let exprs = plan
.expressions()
Copy link
Contributor Author

@alamb alamb Apr 10, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Calling expressions() clones all the expressions

@alamb alamb marked this pull request as ready for review April 10, 2024 13:50
@alamb
Copy link
Contributor Author

alamb commented Apr 10, 2024

@jackwener and @jayzhan211 here the next PR in the "don't copy so much in the optimizer"

///
/// If a rule use default None, it should traverse recursively plan inside itself
/// If returns `None`, the default, the rule must handle recursion itself
fn apply_order(&self) -> Option<ApplyOrder> {
None
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think most of the cases are BottomUp by default?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think most of the cases are BottomUp by default?

we can't assume it.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I agree most of the cases probably should be bottom up (but not all). I'll keep an eye open for this as I work through the other optimizer rules

Copy link
Contributor

@jayzhan211 jayzhan211 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

👍

@jackwener jackwener merged commit 58e0b59 into apache:main Apr 11, 2024
24 checks passed
@alamb alamb deleted the alamb/simplify_exprs_no_copy branch April 11, 2024 10:19
@alamb
Copy link
Contributor Author

alamb commented Apr 11, 2024

Thanks @jackwener and @jayzhan211 -- I assumed it would take some time to review these PRs but you are so efficient!

I plan to spend a little time planning today to write down the remaining tasks (aka rewriting each OptimizerRule to use the new APIs) and then start cranking on them. CommonSubExprEliminate will be a tricky one but another major win I think

appletreeisyellow pushed a commit to influxdata/arrow-datafusion that referenced this pull request Apr 24, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
core Core DataFusion crate optimizer Optimizer rules
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants